Skip to content

feat: parse Q10 archived map packets - #936

Open
hCoureau wants to merge 7 commits into
Python-roborock:mainfrom
hCoureau:feat/q10-archive-packets
Open

hCoureau wants to merge 7 commits into
Python-roborock:mainfrom
hCoureau:feat/q10-archive-packets

Conversation

@hCoureau

@hCoureau hCoureau commented Aug 31, 2026

Copy link
Copy Markdown
Contributor

Q10 clean-record and saved-map responses use different packet markers from live maps. This adds bounded archive parsing and a Q10CleanRecordDetail(map, trace) response so callers receive the map and historical path together without extending the map raster model.

Implementation

  • Classify current, live-trace, clean-record and saved-map markers with Q10MapPacketKind. Unknown values resolve to unknown and are ignored rather than defaulting to a current map.
  • Decode shared raster fields once; clean-record responses compose that map with an optional historical path.
  • Keep Q10HistoricalTracePacket limited to points and heading. Validate wire version/reserved fields internally and do not expose the undecoded wire value.
  • Apply the same conservative stray-leading-point filter used for live paths. Short paths and ordinary origin points are preserved.
  • Render the explicitly supplied map and trace without type-dependent branching or silently ignored arguments.
  • Remove unused archive-marker and carpet-mask helpers; require a decompression output bound and return only the consumed trace model.

#937 consumes the new detail object in its clean-history trait. Saved and live map state remain independent. No private map captures or account data are included.

Dependencies and validation

#933 is merged. Current upstream main (eac001c, including #908) is integrated. This branch also includes the isolated conformance fix in #965, which addresses the independently reproduced upstream failure tracked in #964; please review/merge that small fix first.

  • Full suite: 1349 passed, 53 existing xfailed, 92 snapshots passed.
  • All pre-commit checks, including Ruff and mypy: passed.
  • Wheel and sdist builds: passed.
  • Regression coverage includes unknown/truncated markers, unsupported archive framing, malformed paths, stray-point filtering, and explicit historical-path rendering.
  • No new physical-device run was performed for this revision.

Related: #767.

Comment thread roborock/map/b01_q10_map_parser.py Outdated

@allenporter allenporter left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I am very happy to keep momentum going on this. I am adding additional feedback since this hasn't been moving since my last comment, in case it was missed. I have a lot of time to review during the us holidy weekend.

Comment thread roborock/protocols/b01_q10_protocol.py Outdated
Comment thread roborock/map/b01_q10_map_parser.py Outdated
Comment thread roborock/map/b01_q10_render.py
Comment thread roborock/map/b01_q10_map_parser.py Outdated
Comment thread roborock/map/b01_q10_map_parser.py Outdated
@hCoureau

Copy link
Copy Markdown
Contributor Author

@allenporter Thanks for the detailed feedback, and sorry I missed the earlier comments. Pushed cbd6abc and merged current main.

  • Clean-record maps now have a dedicated Q10CleanRecordMapPacket type; ordinary current/saved maps no longer carry historical_trace. The grid, rooms, erase zones, carpet and calibration are shared across all three map kinds, so those stay in the common base.
  • The renderer reads the historical path directly from the clean-record packet; callers only supply a separate trace for live maps. The consumer in feat: expose Q10 map archives #937 is updated too.
  • decode_message looks up the marker once, the LZ4 output bound is required, and the unused trace-parser return value is removed.

Validation: 999 tests and 92 snapshots passed, all pre-commit checks passed, and wheel/sdist builds passed. The dependent read-only PRs have been updated as well. Could you take another look when you have time, particularly at the shared-map/dedicated-clean-record type boundary?

These maintenance changes were prepared with OpenAI Codex assistance.

@allenporter allenporter left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for iterating on this and splitting out the clean-record path ownership.

Taking a close look at the resulting Q10CleanRecordMapPacket boundary, the **vars(packet) unpacking in parse_map_packet and the isinstance check in render_q10_map feel like an awkward fit for dataclass inheritance. Rather than subclassing Q10MapPacket, modeling this as a composite object Q10CleanRecordDetail(map=Q10MapPacket, trace=Q10HistoricalTracePacket | None) would be significantly cleaner and avoid both constructor duplication and isinstance branches in rendering.

I've also left a few inline comments on RoborockEnum fallback resilience, stripping stray origin points, and trimming internal wire fields from public models.

Comment thread roborock/map/b01_q10_map_parser.py Outdated
Comment thread roborock/map/b01_q10_map_parser.py Outdated
Comment thread roborock/map/b01_q10_map_parser.py Outdated
Comment thread roborock/map/b01_q10_map_parser.py Outdated
Comment thread roborock/map/b01_q10_map_parser.py Outdated
Comment thread roborock/map/b01_q10_render.py Outdated
@hCoureau

Copy link
Copy Markdown
Contributor Author

@allenporter Implemented the requested composition in 4eb0b9b and updated the consumers in #937#939:

  • Q10CleanRecordDetail(map, trace) replaces map inheritance and **vars(packet) construction. Rendering uses the supplied map/path directly, without type-dependent branches or ignored arguments.
  • Q10MapPacketKind now has an explicit unknown member and constant-time lookup; unknown firmware markers are ignored.
  • Historical paths expose only points and heading; version validation stays internal and the opaque wire value is no longer public.
  • Removed the unused archive-marker and carpet-mask helpers.
  • Historical paths use the existing conservative stray-leading-point filter, with tests for the outlier, ordinary origin points, and short paths.

Merged current main and preserved the new position/zone/goto support. Full local validation on #936: 1349 passed, 53 existing xfailed, 92 snapshots passed; pre-commit and package builds passed.

Separately, current main's new model conformance test fails on the existing frozen Q10RoborockPoint. I reproduced that on untouched eac001c, opened #964, and submitted the isolated fix in #965. This branch includes that commit so validation can pass; #965 should land first.

Could you review the revised boundary and parser changes when you have time?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants